package com.example.service;

import com.example.entity.ApiInfo;
import com.example.mapper.ApiMapper;
import io.swagger.v3.oas.models.*;
import io.swagger.v3.oas.models.info.Info;
import io.swagger.v3.oas.models.servers.Server;
import io.swagger.v3.oas.models.parameters.Parameter;
import io.swagger.v3.oas.models.parameters.QueryParameter;
import io.swagger.v3.oas.models.responses.ApiResponse;
import io.swagger.v3.oas.models.responses.ApiResponses;
import io.swagger.v3.oas.models.media.Content;
import io.swagger.v3.oas.models.media.MediaType;
import io.swagger.v3.oas.models.media.StringSchema;
import io.swagger.v3.oas.models.parameters.RequestBody;
import io.swagger.v3.oas.models.tags.Tag;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.ArrayList;
import java.util.Set;
import java.util.HashSet;

@Service
public class SwaggerGenerationService {

    @Autowired
    private ApiMapper apiMapper;

    public OpenAPI generateSwaggerDocument() {
        // 1. 创建OpenAPI根对象
        OpenAPI openAPI = new OpenAPI();
        
        // 2. 设置OpenAPI版本
        openAPI.setOpenapi("3.0.1");
        
        // 3. 设置文档基本信息
        Info info = new Info()
            .title(convertChinesePunctuationToEnglish("数据库驱动的API文档"))
            .version(convertChinesePunctuationToEnglish("1.0.0"))
            .description(convertChinesePunctuationToEnglish("自动从数据库API表生成的OpenAPI文档\n\n" +
                        "该文档包含系统中所有可用的API接口信息，\n" +
                        "可通过接口路径和HTTP方法进行访问。"));
        openAPI.setInfo(info);
        
        // 4. 设置服务器信息
        Server server = new Server()
            .url("https://api.user-center.com/v2")
            .description("用户中心服务（独立服务器）");
        openAPI.setServers(Arrays.asList(server));
        
        // 5. 从数据库查询所有API
        List<ApiInfo> apiList = apiMapper.selectAllApis();
        Paths paths = new Paths();
        
        // 收集所有tags
        Set<String> allTags = new HashSet<>();
        
        for (ApiInfo api : apiList) {
            // 6. 创建路径对象
            PathItem pathItem = new PathItem();
            
            // 处理tags
            List<String> tagList = new ArrayList<>();
            if (api.getTags() != null && !api.getTags().isEmpty()) {
                // 假设tags是以逗号分隔的字符串
                String[] tags = api.getTags().split(",");
                for (String tag : tags) {
                    String trimmedTag = tag.trim();
                    if (!trimmedTag.isEmpty()) {
                        tagList.add(trimmedTag);
                        allTags.add(trimmedTag);
                    }
                }
            }
            
            // 获取HTTP方法
            String method = api.getReqMethod() != null ? api.getReqMethod().toUpperCase() : "GET";
            
            // 7. 创建操作对象，使用operationId字段作为operationId
            io.swagger.v3.oas.models.Operation operation = new io.swagger.v3.oas.models.Operation()
                .operationId(api.getOperationId() != null ? api.getOperationId() : "")  // 使用operationId字段作为operationId
                .summary(convertChinesePunctuationToEnglish(api.getApiName() != null ? api.getApiName() : "未命名接口"))
                .description(formatDescription(convertChinesePunctuationToEnglish(api.getDescription())))
                // 确保这些字段始终存在
                .tags(tagList)  // 使用从数据库读取的tags
                .parameters(Arrays.asList())
                .responses(new ApiResponses());
            
            // 对于非GET方法，添加requestBody
            if (!"GET".equals(method)) {
                operation.requestBody(new RequestBody());
            }
            
            // 设置请求/响应类型
            // 基于协议类型设置produces
            if ("HTTP".equals(api.getProtocolType())) {
                ApiResponses responses = operation.getResponses();
                if (responses == null) {
                    responses = new ApiResponses();
                    operation.setResponses(responses);
                }
                ApiResponse response = new ApiResponse()
                    .description("成功响应")
                    .content(new Content()
                        .addMediaType("application/json", new MediaType()));
                responses.addApiResponse("200", response);
            }
            
            // 10. 将操作绑定到对应的HTTP方法
            switch (method) {
                case "GET":
                    pathItem.setGet(operation);
                    break;
                case "POST":
                    pathItem.setPost(operation);
                    break;
                case "PUT":
                    pathItem.setPut(operation);
                    break;
                case "DELETE":
                    pathItem.setDelete(operation);
                    break;
                default:
                    pathItem.setGet(operation);
                    break;
            }
            
            // 11. 添加路径到路径集合
            // 使用url_path作为API路径，如果为空则使用call_url
            String apiPath = api.getUrlPath();
            if (apiPath == null || apiPath.isEmpty()) {
                apiPath = api.getCallUrl();
            }
            
            if (apiPath != null && !apiPath.isEmpty()) {
                paths.addPathItem(apiPath, pathItem);
            }
        }
        
        // 构建tags列表
        List<Tag> tagList = new ArrayList<>();
        for (String tagName : allTags) {
            Tag tag = new Tag();
            tag.setName(tagName);
            tagList.add(tag);
        }
        openAPI.setTags(tagList);
        
        openAPI.setPaths(paths);
        return openAPI;
    }
    
    /**
     * 格式化描述信息，添加适当的换行和空格
     * @param description 原始描述
     * @return 格式化后的描述
     */
    private String formatDescription(String description) {
        if (description == null || description.isEmpty()) {
            return "No description available";
        }
        
        // 如果描述中没有换行符，我们可以在适当位置添加换行
        if (!description.contains("\n")) {
            // 在句号后添加换行符以提高可读性
            return description.replaceAll("\\.\\s*", ".\n");
        }
        
        return description;
    }
    
    /**
     * 将中文标点符号转换为英文标点符号
     * @param text 包含中文标点的文本
     * @return 转换后的文本
     */
    private String convertChinesePunctuationToEnglish(String text) {
        if (text == null) {
            return null;
        }
        
        return text
            .replace("，", ",")
            .replace("。", ".")
            .replace("；", ";")
            .replace("：", ":")
            .replace("？", "?")
            .replace("！", "!")
            .replace("“", "\"")
            .replace("”", "\"")
            .replace("‘", "'")
            .replace("’", "'")
            .replace("（", "(")
            .replace("）", ")")
            .replace("【", "[")
            .replace("】", "]")
            .replace("《", "<")
            .replace("》", ">")
            .replace("、", ",")
            .replace("…", "...")
            .replace("—", "-")
            .replace("·", ".");
    }
}